﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.IO;
using System.Text.RegularExpressions;

namespace RegexBatchReplacer
{
    public partial class MainForm : Form
    {
        Regex _regex;

        public MainForm()
        {
            InitializeComponent();
        }

        private void btnBrowse_Click(object sender, EventArgs e)
        {
            if (dlgFolder.ShowDialog() == System.Windows.Forms.DialogResult.OK)
            {
                txDirectory.Text = dlgFolder.SelectedPath;
            }
        }

        private void btnGo_Click(object sender, EventArgs e)
        {
            //validating
            string dir = txDirectory.Text;
            if (string.IsNullOrEmpty(dir)) return;

            string filter = txFilter.Text;
            if (string.IsNullOrEmpty(filter)) return;

            string pattern = txPattern.Text;
            if (string.IsNullOrEmpty(pattern)) return;

            string replacement = txReplace.Text;

            if (!Directory.Exists(dir)) return;
            
            //lets go
            _regex = new Regex(pattern, RegexOptions.Compiled);

            progressBar1.Visible = true;
            btnGo.Enabled = false;
            statusLbl.Text = "Processing...";
            
            ProcessDir(dir, filter, replacement);
            
            progressBar1.Visible = false;
            statusLbl.Text = "Done! Ready";
            btnGo.Enabled = true;
        }

        private void ProcessDir(string dir, string filter, string replacement)
        {
            //process files one by one
            string[] files = Directory.GetFiles(dir, filter);
            progressBar1.Maximum = files.Length;
            for (int i = 0; i < files.Length; i++)
            {
                ProcessFile(files[i], replacement);
                progressBar1.Value = i;
                Application.DoEvents();
            }

            if (cbRecursive.Checked)
            {
                foreach (string subdir in Directory.GetDirectories(dir))
                {
                    ProcessDir(subdir, filter, replacement);
                }
            }
        }

        private void ProcessFile(string fileName, string replacement)
        {
            FileInfo fi = new FileInfo(fileName);
            if (fi.IsReadOnly) return;

            string fileText;
            using (StreamReader sr = File.OpenText(fileName))
            {
                fileText = sr.ReadToEnd();
                sr.Close();
            }

            if (_regex.IsMatch(fileText))
            {
                fileText = _regex.Replace(fileText, replacement);
                try
                {
                    using (StreamWriter sw = File.CreateText(fileName))
                    {
                        sw.Write(fileText);
                        sw.Close();
                    }
                }
                catch (Exception ex)
                {
                    MessageBox.Show(string.Format("Error writing to file {0}:\n\n{1}", fileName, ex.ToString()));
                }
            }
        }
    }
}
